#include "CameraController.h"
#include "NeroEngine\NInput.h"
#include "DirectX\Camera.h"

#ifdef WIN32
#include "Win32\Win32Input.h"
#endif

RTTI_DEFINITIONS(CameraController)

extern Engine::NInput* GInput;

using namespace System;

CameraController::CameraController(void)
	:Game::NComponent()
{
}

CameraController::~CameraController(void)
{
}

void CameraController::Initialize(Engine::NEntity* owner)
{
	NComponent::Initialize(owner);

	mBinding[0].ID = KEY::KEY_W;
	mBinding[0].Action = Action::ACTION_FOWARD;

	mBinding[1].ID = KEY::KEY_A;
	mBinding[1].Action = Action::ACTION_STRAFE_LEFT;

	mBinding[2].ID = KEY::KEY_S;
	mBinding[2].Action = Action::ACTION_BACK;

	mBinding[3].ID = KEY::KEY_D;
	mBinding[3].Action = Action::ACTION_STRAFE_RIGHT;

	mBinding[4].ID = KEY::KEY_R;
	mBinding[4].Action = Action::ACTION_RESET;

	Enable();
}

void CameraController::Deinitialize()
{
}

void CameraController::Update(float)
{
	if(mOwner && GInput && mIsEnabled)
	{
		Graphics::Camera* camera = mOwner->As<Graphics::Camera>();
		if(!camera)
		{
			return;
		}

		for(int i = 0; i < ACTION_COUNT; i++)
		{
			if(	GInput->IsKeyDown(mBinding[i].ID))
			{
				switch (mBinding[i].Action)
				{
				case Action::ACTION_FOWARD:
					camera->Move(NVector3(0.0f, 0.0f, 1.0f));
					break;
				case Action::ACTION_STRAFE_LEFT:
					camera->Move(NVector3(1.0f, 0.0f, 0.0f));
					break;
				case Action::ACTION_BACK:
					camera->Move(NVector3(0.0f, 0.0f, -1.0f));
					break;
				case Action::ACTION_STRAFE_RIGHT:
					camera->Move(NVector3(-1.0f, 0.0f, 0.0f));
					break;
				case Action::ACTION_RESET:
					camera->SetPosition(NVector3(-10.0f, 0.0f, 0.0f));
					camera->SetLookAt(NVector3(0.0f, 0.0f, 0.0f));
					camera->SetOrientation(NVector3(0.0f, 1.0f, 0.0f));
					camera->SetRight(NVector3(0.0f, 0.0f, 1.0f));
					camera->SetDirection(NVector3(1.0f, 0.0f, 0.0f));
					break;
				default:
					break;
				}
			}
#ifdef WIN32
			System::Win32Input* winInput = (System::Win32Input*)GInput;
			if(winInput)
			{
				static float rotationRate = 0.001f;
				System::Mouse* mouse = winInput->GetMouse();
				if(mouse)
				{
					camera->Rotate(NVector2(-(mouse->DeltaX() * rotationRate), mouse->DeltaY() * rotationRate));
				}
			}
#endif
		}
	}
}